#include "CoCoA/library.H"
#include <cstdlib>
#include <ctime>
#include <string>
#include <set>
#include <sstream>


using namespace CoCoA;
using namespace std;


string ConvertToString(const RingElem & r){
			ostringstream oStr;
			oStr << r;
			return oStr.str();
}



set<string> myindets(const CoCoA::PolyRing R){
	set<string> Indets;
	const vector<CoCoA::RingElem>& vars = indets(R);
	for (size_t i=0; i<vars.size(); i++)
		Indets.insert(ConvertToString(vars[i])); //log
	return Indets;
}

static const int MAXDEG=10;
static const int MAXCF=99;
RingElem randpoly(const string& v){
	//const vector<symbol> syms={v};	
	SparsePolyRing R = NewPolyRing(RingQ(), symbols(v));
	const vector<RingElem>& vars = indets(R);
	RingElem vp = vars[0],f(R);
	int deg=1+rand() % MAXDEG;
	for (int i=0; i<deg+1; i++)
			f+=(rand() % MAXCF )*power(vp,rand() % deg);
	return f;
}


/*template <class T>
   void coutprint (const T& o) {cout << o;}
*/
ostream& coutprint (const RingElem& r) {cout << r; return cout;}

void program()
{
  GlobalManager CoCoAFoundations;
  string vars[3]={"x","y","z"};
  //vector<string> vars("x","y","z");
  PolyRing R = NewPolyRing(RingQ(), symbols("x1","y1","z_2"));
  srand (time(NULL));
  // RingElem f=randpoly(vars[rand() % 3]);
  RingElem f=indet(R,0)+indet(R,1);
  GlobalOutput() << "The random generated polynomial is: " << f << endl;
  GlobalOutput() << "The indets of: " << f << " are:" << endl;
  set<string> Indets = myindets(R);
  for (set<string>::const_iterator i=Indets.begin(); i != Indets.end();i++)
		  GlobalOutput() << "\t" << *i;
  GlobalOutput() << endl;

  vector<RingElem> Inds=indets(R);
  // set<RingElem> rs(Inds.begin(),Inds.end());
  /*for (set<RingElem>::const_iterator ir=rs.begin(); ir != rs.end();ir++)
		  GlobalOutput() << "\t" << *ir;
  GlobalOutput() << endl;*/
  GlobalOutput() << "again: " <<  endl;
  for_each(Inds.begin(),Inds.end(),coutprint);
}

int main()
{
  try
  {
    program();
    return 0;
  }
  catch (const CoCoA::ErrorInfo& err)
  {
    GlobalErrput() << "***ERROR***  UNCAUGHT CoCoA error";
    ANNOUNCE(err);
  }
  catch (const std::exception& exc)
  {
    GlobalErrput() << "***ERROR***  UNCAUGHT std::exception: " << exc.what() << endl;
  }
  catch(...)
  {
    GlobalErrput() << "***ERROR***  UNCAUGHT UNKNOWN EXCEPTION" << endl;
  }
  return 1;
}

//----------------------------------------------------------------------
// RCS header/log in the next few lines
// $Header: /Volumes/Home_1/cocoa/cvs-repository/CoCoALib-0.99/examples/ex-factor1.C,v 1.1 2009/09/23 14:09:36 abbott Exp $
// $Log: ex-factor1.C,v $
// Revision 1.1  2009/09/23 14:09:36  abbott
// First example for (polynomial) factorization.
//
//

